package org.ioriframework.plugin.maven.util;

import java.util.HashMap;
import java.util.Map;

import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.Node;
import org.dom4j.XPath;
import org.dom4j.io.SAXReader;
import org.eclipse.core.resources.IProject;
import org.eclipse.core.resources.IWorkspace;
import org.eclipse.core.resources.IWorkspaceRoot;
import org.eclipse.core.resources.ResourcesPlugin;
import org.ioriframework.plugin.maven.Constants;
import org.ioriframework.plugin.maven.console.ConsoleService;

/**
 * Maven工具类
 * @author iori
 *
 */
public class MavenUtils {
	
	/**
	 * 获取maven目录
	 * @return
	 */
	public static String getMavenHome() {
		// 从首选项中取Maven目录
		String mavenHome = PreferenceUtils.getString(Constants.P_MAVEN_HOME);
		// 如果无法找到maven目录，抛出异常
		if (StringUtils.isNullOrEmpty(mavenHome)) {
			throw new RuntimeException("[ERROR] 无法找到maven目录，请在首选项中配置MAVEN_HOME");
		}
		// 目录精确到mvn命令
		mavenHome += "/bin/mvn";
		// 如果是windows系统，则加上cmd后缀
		if (OSUtils.isWindows()) {
			mavenHome += ".cmd";
		}
		return mavenHome;
	}
	

	/**
	 * 获取指定类型项目的信息
	 * @return
	 */
	public static Map<String, String> findProjectInfo(String packaging) {
		// 获取工作空间中的所有项目
		IWorkspace workspace = ResourcesPlugin.getWorkspace();
		IWorkspaceRoot root = workspace.getRoot();
		IProject[] projects = root.getProjects();
		// 如果没有项目，返回null
		if (projects == null || projects.length < 1) {
			return null;
		}
		Map<String, String> map = new HashMap<String, String>();
		// 找工作空间中packagingType为pom的项目，代表是parent项目
		for (IProject project : projects) {
			if (project.isOpen()) {
				String pomPath = project.getLocation() + "/pom.xml";
				try {
					String packagingType = MavenUtils.findPackaging(pomPath);
					if (packaging.equals(packagingType)) {
						// 项目名称
						map.put("parentProjectName", project.getName());
						// pom.xml全路径
						map.put("parentPomPath", pomPath);
						// XXX 目前只取工作空间中的一个项目打包
						break;
					}
				} catch (Exception e) {
					ConsoleService.printlnWarning2Console("[WARNING]获取packagingType失败，此项目不是maven项目. " + e.getMessage());
				}
			}
		}
		return map;
	}

	/**
	 * 获取项目类型
	 * @param pomPath
	 * @return
	 * @throws DocumentException
	 */
	public static String findPackaging(String pomPath) throws DocumentException {
		String path = "//POM:packaging";
		return findPomConfig(pomPath, path);
	}
	
	/**
	 * 获取Jetty运行时占用的端口
	 * @param pomPath
	 * @return
	 * @throws DocumentException
	 */
	public static Integer findRunPort(String pomPath) throws DocumentException {
		String path = "//POM:*[name()='httpConnector']/*[name()='port']";
		try {
			return Integer.valueOf(findPomConfig(pomPath, path));
		} catch (NullPointerException e) {
			throw new RuntimeException("Pom.xml中运行jetty插件的端口[port]没有配置");
		} catch (Exception e) {
			throw new RuntimeException("Pom.xml中运行jetty插件的端口[port]配置不正确");
		}
	}
	
	/**
	 * 获取Jetty停止时占用的端口
	 * @param pomPath
	 * @return
	 * @throws DocumentException
	 */
	public static Integer findStopPort(String pomPath) throws DocumentException {
		String path = "//POM:*[name()='plugin']/*[name()='configuration']/*[name()='stopPort']";
		try {
			return Integer.valueOf(findPomConfig(pomPath, path));
		} catch (NullPointerException e) {
			throw new RuntimeException("Pom.xml中停止jetty插件的端口[stopPort]没有配置");
		} catch (Exception e) {
			throw new RuntimeException("Pom.xml中停止jetty插件的端口[stopPort]配置不正确");
		}
	}
	
	/**
	 * 获取POM文件对应路径的配置
	 * @param pomPath
	 * @return
	 * @throws DocumentException
	 */
	public static String findPomConfig(String pomPath, String path) throws DocumentException {
		SAXReader saxReader = new SAXReader();
		Document document = saxReader.read(pomPath);
		Map<String, String> nsMap = new HashMap<>();
		// 设置命名空间
		nsMap.put("POM", "http://maven.apache.org/POM/4.0.0");
		// 获取packaging节点
		XPath xpath = document.createXPath(path);
		xpath.setNamespaceURIs(nsMap);
		Node node = xpath.selectSingleNode(document);
		return node.getText();
	}
	
}
